﻿/*
    This file is part of News Worm.

    News Worm is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    News Worm is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with News Worm.  If not, see <http://www.gnu.org/licenses/>.
 */

using System;
using System.Net;
using System.Threading;
using System.Linq;
using System.Text;

namespace NewsWorm {
    internal class WebServer {

        private readonly HttpListener m_Listener = new HttpListener();
        private readonly Func<HttpListenerRequest, string> m_ResponderMethod;

        internal WebServer( string[] prefixes, Func<HttpListenerRequest, string> method ) {
            if ( !HttpListener.IsSupported )
                throw new NotSupportedException(
                    "Needs Windows XP SP2, Server 2003 or later." );

            if ( prefixes == null || prefixes.Length == 0 )
                throw new ArgumentException( "prefixes" );

            if ( method == null )
                throw new ArgumentException( "method" );

            foreach ( string s in prefixes )
                m_Listener.Prefixes.Add( s );

            m_ResponderMethod = method;
            m_Listener.Start();
        }

        internal WebServer( Func<HttpListenerRequest, string> method, params string[] prefixes )
            : this( prefixes, method ) { }

        internal void Start() {
            ThreadPool.QueueUserWorkItem( ( o ) => {
                Console.WriteLine( "Webserver running..." );
                try {
                    while ( m_Listener.IsListening ) {
                        ThreadPool.QueueUserWorkItem( ( c ) => {
                            var ctx = c as HttpListenerContext;
                            try {
                                string rstr = m_ResponderMethod( ctx.Request );
                                byte[] buf = Encoding.UTF8.GetBytes( rstr );
                                ctx.Response.ContentLength64 = buf.Length;
                                ctx.Response.OutputStream.Write( buf, 0, buf.Length );
                            } catch { }
                            finally {
                                ctx.Response.OutputStream.Close();
                            }
                        }, m_Listener.GetContext() );
                    }
                } catch { }
            } );
        }

        public void Stop() {
            m_Listener.Stop();
            m_Listener.Close();
        }

    }
}
